package com.example.udptestdemo;


import java.io.File;
import java.io.FileInputStream;
import java.math.BigInteger;
import java.net.DatagramPacket;
import java.net.InetAddress;
import java.net.SocketException;
import java.net.UnknownHostException;
import java.security.MessageDigest;

import org.greenrobot.eventbus.EventBus;
import org.greenrobot.eventbus.Subscribe;
import org.greenrobot.eventbus.ThreadMode;
import org.json.JSONObject;

import android.app.Activity;
import android.graphics.Bitmap;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.text.format.Formatter;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

import com.example.udptestdemo.events.SendResumeFileEvent;
import com.example.udptestdemo.listeners.FinishListener;
import com.example.udptestdemo.listeners.MonitorRefreshListener;
import com.example.udptestdemo.listeners.ProgressListener;
import com.example.udptestdemo.runnables.MonitorRunnable;
import com.example.udptestdemo.runnables.SendFileRunnable;
import com.example.udptestdemo.runnables.SendResumeFileRunnable;
import com.example.udptestdemo.servers.ADPlayerSocket;
import com.example.udptestdemo.utils.DataFormat;
import com.example.udptestdemo.utils.FileUtil;

public class MainActivity extends Activity implements OnClickListener{

	
	private ADPlayerSocket  mAdSocket;
	private MyProgressBar myProgress;
	private TextView progressText, maxText;//进度条当前进度，最大值
	private Button btnSendFile,btnCancelSend , btnMonitorBegin;//发送文件，取消发送
	private EditText editIpAddress;//输入ip地址
	private ImageView mImgShow;
	String filePath = "/mnt/internal_sd/program/qqqqqq.zip";
	
	
	private MonitorRunnable mMonitorRunnable;
	private SendResumeFileRunnable mSendResumeFileRunnable;
	
	private SendFileRunnable mSendFileRunnable;
	
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		FileUtil.initFilePath();
		setContentView(R.layout.activity_main);
		initView();
		runUdpServer();
		EventBus.getDefault().register(this);
	}
	/**
	 * 初始化控件
	 */
	void initView(){
		myProgress = (MyProgressBar)findViewById(R.id.pgsBar);
		progressText = (TextView)findViewById(R.id.progressText);
		maxText = (TextView)findViewById(R.id.maxText);
		btnSendFile = (Button)findViewById(R.id.send_file_btn);
		btnCancelSend = (Button)findViewById(R.id.cancel_file_btn);
		editIpAddress = (EditText)findViewById(R.id.edit_address);
		btnMonitorBegin =(Button)findViewById(R.id.btn_monitor_begin);
		mImgShow=(ImageView) findViewById(R.id.img_show);
		editIpAddress.setText("192.168.1.57");
		btnSendFile.setOnClickListener(this);
		btnMonitorBegin.setOnClickListener(this);
	}
	/**
	 * 进度条回调
	 */
	ProgressListener progressListener = new ProgressListener() {
		
		@Override
		public void progessChanged(long send_size, long total) {
			Log.d("progressListener", "send_size:"+send_size+" total:"+total);
			Message msg = handler.obtainMessage();
			msg.obj = send_size;
			msg.what = 0;
			handler.sendMessage(msg);
		}
	};
	/**
	 * 更新进度条
	 */
	Handler handler = new Handler(){
		@Override
		public void handleMessage(Message msg) {
			switch (msg.what) {
			case 0:
				long send_size = (Long) msg.obj;
				if (send_size > myProgress.getMax()) {
					send_size = myProgress.getMax();
				}
				myProgress.setProgress((int) send_size);
				progressText.setText(getFileSize(send_size));
				break;
			case 1:
				boolean success = (Boolean) msg.obj;
				Toast.makeText(MainActivity.this, "success:"+success, Toast.LENGTH_SHORT).show();
				break;
				
			case 2:
				Bitmap bitmap= FileUtil.readBitMap(FileUtil.MonitorFileTemp);
				mImgShow.setImageBitmap(bitmap);
				break;
			case 3:
				if(msg.arg1==1){
					Toast.makeText(MainActivity.this, "Monitor finish Success ", Toast.LENGTH_SHORT).show();
				}else{
					Toast.makeText(MainActivity.this, "error:"+String.valueOf(msg.obj), Toast.LENGTH_SHORT).show();
				}
				break;
			default:
				break;
			}
		}
	};
	/**
	 * 结束回调
	 */
	FinishListener finishListener = new FinishListener() {
		@Override
		public void finish(boolean success,String error) {
			Message msg = handler.obtainMessage();
			msg.what = 1;
			msg.obj = success;
			handler.sendMessage(msg);
		}
	};
	
	
	private void runUdpServer(){
		try {
			mAdSocket=new ADPlayerSocket(12017, 1000*10);
		} catch (SocketException e) {
			e.printStackTrace();
		}
		
		mAdSocket.startWork();
	}
	
	
	
	/**
	 * 接受回执开始运行发送文件runnable
	 * @param event
	 */
	@Subscribe(threadMode = ThreadMode.ASYNC)
	public void onEvent(SendResumeFileEvent event){
		mSendResumeFileRunnable.updateReciveSize(event.RecivedFileSize,event.mRemoteAddress,event.mRemotePort);
		new Thread(mSendResumeFileRunnable).start();
	}
	/**
	 * 发送断点续传文件
	 */
	private void sendResumeFile(){
		File file = new File(filePath);
		myProgress.setMax((int) file.length());
		maxText.setText(getFileSize(file.length()));
		new Thread(new SendResumeRunnable(file)).start();
	}
	
	
	private void sendFile(){
		File file = new File(filePath);
		myProgress.setMax((int) file.length());
		maxText.setText(getFileSize(file.length()));
		new Thread(new SendResumeRunnable(file)).start();
	}
	
	/**
	 * 进度条单位转换
	 * 
	 * @return
	 */

	private String getFileSize(long fileSize) {
		String size = "";
		size = Formatter.formatFileSize(getBaseContext(), fileSize);
		return size;
	}

	@Override
	protected void onStop() {
		super.onStop();
		mAdSocket.onRelease();
	}

	@Override
	public void onClick(View v) {
		switch (v.getId()) {
		case R.id.send_file_btn:
			// 将进度条的进度清空
			myProgress.setProgress(0);
			progressText.setText("");
			sendResumeFile();
			break;
		case R.id.cancel_file_btn:
			break;
		case R.id.btn_monitor_begin:
			InetAddress addr;
			try {
				addr = InetAddress.getByName("192.168.1.62");
				if(mMonitorRunnable!=null)
					mMonitorRunnable.onDestory();
				mMonitorRunnable = new MonitorRunnable(mAdSocket,addr , 12017);
				mMonitorRunnable.setListener(new MonitorRefreshListener() {
					
					@Override
					public void monitor_refresh() {
						Message msg = handler.obtainMessage();
						msg.what=2;
						handler.sendMessage(msg);
					}
				}, new FinishListener() {
					
					@Override
					public void finish(boolean success, String content) {
						Message msg = handler.obtainMessage();
						msg.what=3;
						msg.arg1 = success?1:0;
						msg.obj=content;
						handler.sendMessage(msg);
					}
				});
				mAdSocket.setMonitorRunnable(mMonitorRunnable);
				new Thread(mMonitorRunnable).start();
				
			} catch (UnknownHostException e) {
				e.printStackTrace();
			}
			
			
			break;
		default:
			break;
		}
	}
	@Override
	protected void onStart() {
		super.onStart();
		myProgress.setProgress(0);
		progressText.setText("");
		//sendFile();
	}
	
	/**
	 * 获取单个文件的MD5值！
	 * 
	 * @param file
	 * @return
	 */
	public static String getFileMD5(File file) {
		if (!file.isFile()) {
			return null;
		}
		MessageDigest digest = null;
		FileInputStream in = null;
		byte buffer[] = new byte[1024];
		int len;
		try {
			digest = MessageDigest.getInstance("MD5");
			in = new FileInputStream(file);
			while ((len = in.read(buffer, 0, 1024)) != -1) {
				digest.update(buffer, 0, len);
			}
			in.close();
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}

		byte[] resultByte = digest.digest();

		BigInteger bigInt = new BigInteger(1, digest.digest());
		return byteArrayToHex(resultByte);
	}

	
	public static String byteArrayToHex(byte[] byteArray) {

		// 首先初始化一个字符数组，用来存放每个16进制字符

		char[] hexDigits = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
				'a', 'b', 'c', 'd', 'e', 'f' };

		// new一个字符数组，这个就是用来组成结果字符串的（解释一下：一个byte是八位二进制，也就是2位十六进制字符（2的8次方等于16的2次方））
		char[] resultCharArray = new char[byteArray.length * 2];

		// 遍历字节数组，通过位运算（位运算效率高），转换成字符放到字符数组中去
		int index = 0;

		for (byte b : byteArray) {

			resultCharArray[index++] = hexDigits[b >>> 4 & 0xf];

			resultCharArray[index++] = hexDigits[b & 0xf];

		}

		// 字符数组组合成字符串返回

		return new String(resultCharArray);
	}
	/**
	 * 发送文件
	 * @author mac
	 *
	 */
	class SendResumeRunnable implements Runnable{
		File file = null;
		public SendResumeRunnable(File file){
			this.file = file;
		}
		@Override
		public void run() {
			String ipAddress = editIpAddress.getText().toString().trim();
			JSONObject jsonObject = new JSONObject();
			try {
				jsonObject.put("file_size", file.length());
				jsonObject.put("file_path", filePath);
				jsonObject.put("cmd", 2);
				jsonObject.put("file_name", "qqqqqq.zip");
				jsonObject.put("file_md5",getFileMD5(file));
				byte[] sendByte = DataFormat.formatCommand(jsonObject.toString());
				InetAddress addr = InetAddress.getByName(ipAddress);
				DatagramPacket packet = new DatagramPacket(sendByte,sendByte.length,addr,12017);
				mAdSocket.sendDatagramPacket(packet);
			} catch (Exception e) {
				e.printStackTrace();
			}
			mSendResumeFileRunnable= new SendResumeFileRunnable(filePath, mAdSocket,progressListener,finishListener);
			mAdSocket.setSendResumeFileRunnable(mSendResumeFileRunnable);
		}
		
	}
	
	
	class SendRunnable implements Runnable{
		File file = null;
		public SendRunnable(File file){
			this.file=file;
		}

		@Override
		public void run() {
			String ipAddress = editIpAddress.getText().toString().trim();
			JSONObject jsonObject = new JSONObject();
			try {
				jsonObject.put("cmd", 4);
				jsonObject.put("file_name", "qqqqqq.zip");
				byte[] sendByte = DataFormat.formatCommand(jsonObject.toString());
				InetAddress addr = InetAddress.getByName(ipAddress);
				DatagramPacket packet = new DatagramPacket(sendByte,sendByte.length,addr,12017);
				mAdSocket.sendDatagramPacket(packet);
			} catch (Exception e) {
				e.printStackTrace();
			}
			
			mSendFileRunnable = new SendFileRunnable(filePath, mAdSocket, progressListener, finishListener);
			
		}
		
	}

}
